// DMPluginWrapper.h

#pragma once

#include "dmalgointerfaces.h"


using namespace System;
using namespace System::Reflection;
using namespace System::Runtime::InteropServices;

#include "DMEnumerationWrappers.h"

namespace Microsoft
{
namespace SqlServer
{
namespace DataMining
{
namespace PluginAlgorithms
{
	ref class AlgorithmNavigationBase;






    
	///////////////////////////////////////////////////////////
	// AlgorithmBase -- Implements IDMAlgorithm
	public  ref class AlgorithmNavigationBase abstract : 
							public ICLR_DMDAGNavigation,
                            public ICLR_DMAlgorithmNavigation,
							public ICLR_SupportErrorInfo
							
	{
	protected:
		// Constructor
        AlgorithmNavigationBase();

	public:


		virtual HRESULT ExportedMoveToNextTree()sealed;


		virtual HRESULT ExportedGetNodeID(
				DM_DAGNodeID*	out_pNodeID)sealed;


		virtual HRESULT	ExportedLocateNode(
				DM_DAGNodeID			in_NodeID)sealed;
		

		virtual HRESULT ExportedValidateNodeID(
				DM_DAGNodeID			in_NodeID)sealed;
		

		virtual HRESULT ExportedGetParentCount(
				ULONG *				out_pulParents)sealed;
		

		virtual HRESULT ExportedMoveToParent(
				ULONG					in_ParentIndex)sealed;
		

		virtual HRESULT ExportedGetParentNodeID	(
				ULONG					in_ParentIndex,
				DM_DAGNodeID *		out_pNodeID)sealed;
		

		virtual HRESULT ExportedGetChildCount(
				ULONG *				out_pulChilds)sealed;
		

		virtual HRESULT ExportedMoveToChild	(
				ULONG					in_ChildIndex)sealed;
		

		virtual HRESULT ExportedGetChildNodeID(
				ULONG					in_ChildIndex,
				DM_DAGNodeID *		out_pNodeID)sealed;
		

		virtual HRESULT ExportedMoveToNextLeaf(
				DM_DAGNodeID			in_ScopeNodeID)sealed;
		

		virtual HRESULT	ExportedAddRefNodeID(
				DM_DAGNodeID			in_NodeID)sealed;
		

		virtual HRESULT	ExportedReleaseNodeID(
				DM_DAGNodeID			in_NodeID)sealed;


		
		virtual HRESULT ExportedGetNodeProperty				(
				IDMContextServices*	in_pContext, 
				DM_NODE_PROP			in_PropID, 
				DMVariantPtr			io_pValue)sealed;

		// retrieves the array property, Return S_FALSE if property not supported
		virtual HRESULT ExportedGetNodeArrayProperty		(
				IDMContextServices*	in_pContext, 
				DM_NODE_PROP			in_PropID, 
				ULONG *				out_pulArraySize,
				void **				out_prgArrayBuffer)sealed;
		
		
		virtual HRESULT ExportedGetNodeUniqueName			(
				IDMContextServices*	in_pContext, 
				DMString *			io_pstrUniqueName)sealed;
		
		
		virtual HRESULT ExportedGetNodeIDFromUniqueName		(
				IDMContextServices*	in_pContext, 
				DMString *			in_pstrUniqueName,
				DM_DAGNodeID *		out_pNodeID)sealed;
		
		
		
		virtual HRESULT ExportedGetUniqueNameFromNodeID		(
				IDMContextServices*	in_pContext, 
				DM_DAGNodeID 			in_NodeID,
				DMString *			out_pstrUniqueName)sealed;

		//ISupportErrorInfo interface
		virtual HRESULT ExportedInterfaceSupportsErrorInfo(
				REFIID			riid)sealed;
	
	protected:
		virtual	System::Boolean				MoveToNextTree()							=	0;
		virtual System::Int32				GetCurrentNodeId()							=	0;
		virtual System::Boolean				LocateNode(System::Int32 nodeId)			=	0;
		virtual System::Boolean				ValidateNodeId(System::Int32 nodeId)		=	0;

		virtual System::UInt32				GetParentCount()							=	0;
		virtual void						MoveToParent(System::UInt32	parentIndex)	=	0;
		virtual System::Int32				GetParentNodeId(System::UInt32	parentIndex)=	0;
		
		virtual System::UInt32				GetChildrenCount()							=	0;
		virtual void						MoveToChild(System::UInt32	childIndex)		=	0;
		virtual System::Int32				GetChildNodeId(System::UInt32	childIndex)	=	0;

		// Node Properties
		virtual NodeType					GetNodeType()									=	0;

		virtual String ^				GetStringNodeProperty(NodeProperty	property)	=	0;
		virtual System::Double				GetDoubleNodeProperty(NodeProperty	property)	=	0;
		
		virtual array<System::UInt32>^		GetNodeAttributes()	{return nullptr;}

		virtual array<AttributeStatistics^>^	GetNodeDistribution()					=	0;
		virtual String ^				GetNodeUniqueName()								=	0;
		virtual String ^				GetUniqueNameFromNodeId(System::Int32 nodeId)	=	0;
		virtual	System::Int32				GetNodeIdFromUniqueName( String ^ nodeUniqueName)	=	0;
	
	private:
		HRESULT	InternalGetNodeDistribution(
				ULONG *				out_pulArraySize,
				void **				out_prgArrayBuffer);
		HRESULT	InternalGetNodeAttributes(
				ULONG *				out_pulArraySize,
				void **				out_prgArrayBuffer);
	};
}
}
}
}